﻿using System;
using System.Collections.Generic;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Xml;
using MxWeiXinPF;
using MxWeiXinPF.Common;
using MxWeiXinPF.Web.admin.sms;
using MxWeiXinPF.Web.api.payment.wxpay;
using Senparc.Weixin.Entities;
using Senparc.Weixin.MP.CommonAPIs;

namespace WxPayAPI
{
    /// <summary>
    /// 支付结果通知回调处理类
    /// 负责接收微信支付后台发送的支付结果并对订单有效性进行验证，将验证结果反馈给微信支付后台
    /// </summary>
    public class ResultNotify:Notify
    {
        public ResultNotify(Page page):base(page)
        {
        }

        public override void ProcessNotify()
        {
            WxPayData notifyData = GetNotifyData();

            //检查支付结果中transaction_id是否存在
            if (!notifyData.IsSet("transaction_id"))
            {
                //若transaction_id不存在，则立即返回结果给微信支付后台
                WxPayData res = new WxPayData();
                res.SetValue("return_code", "FAIL");
                res.SetValue("return_msg", "支付结果中微信订单号不存在");
                Log.Error(this.GetType().ToString(), "The Pay result is error : " + res.ToXml());
                page.Response.Write(res.ToXml());
                page.Response.End();
            }

            string transaction_id = notifyData.GetValue("transaction_id").ToString();

            //查询订单，判断订单真实性
            if (!QueryOrder(transaction_id))
            {
                //若订单查询失败，则立即返回结果给微信支付后台
                WxPayData res = new WxPayData();
                res.SetValue("return_code", "FAIL");
                res.SetValue("return_msg", "订单查询失败");
                Log.Error(this.GetType().ToString(), "Order query failure : " + res.ToXml());
                page.Response.Write(res.ToXml());
                page.Response.End();
            }
            //查询订单成功
            else
            {
                string tradeno = "";
                try
                {
                    tradeno = notifyData.GetValue("out_trade_no").ToString();
                    //处理业务
                    Buisiness(tradeno);
                }
                catch (Exception ex)
                {
                    LogHelper.WriteLog(typeof(ResultNotify), "处理业务订单业务失败,订单号="+ tradeno);
                   
                }
                WxPayData res = new WxPayData();
                res.SetValue("return_code", "SUCCESS");
                res.SetValue("return_msg", "OK");
                Log.Info(this.GetType().ToString(), "order query success : " + res.ToXml());
                page.Response.Write(res.ToXml());
                page.Response.End();


            }
        }

        private void Buisiness(string transactionid)
        {
            try
            {
                MxWeiXinPF.Model.orders ordertmp = new MxWeiXinPF.Model.orders();
                MxWeiXinPF.BLL.orders otBll = new MxWeiXinPF.BLL.orders();
                ordertmp = otBll.GetModelByTranid(transactionid);
                if (ordertmp != null && ordertmp.payment_status != 2)
                {
                    ordertmp.payment_status = 2;
                    ordertmp.status = 2;
                    if (otBll.Update(ordertmp))
                    {
                        LogHelper.WriteLog(typeof(ResultNotify), "订单状态修改成功,订单编号:" + ordertmp.id);

                        TransferToShopMgr(ordertmp);
                        SendMsg(ordertmp);
                    }
                    else
                    {
                        LogHelper.WriteLog(typeof(ResultNotify), "订单状态修改失败,订单编号:" + ordertmp.id);
                    }

                }
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(typeof(ResultNotify), ex);
            }

        }
        private void TransferToShopMgr(MxWeiXinPF.Model.orders morder)
        {
            try
            {
                if (morder.shopid == 39)
                {
                    LogHelper.WriteLog(typeof(ResultNotify), "易药宝的订单,无需转账");
                    return;
                }
                MxWeiXinPF.BLL.dt_transfer otTran = new MxWeiXinPF.BLL.dt_transfer();
                MxWeiXinPF.Model.dt_transfer mdt = new MxWeiXinPF.Model.dt_transfer();
                mdt.create_time = DateTime.Now;
                mdt.status = 0;
                mdt.orderid = morder.id;
                mdt.shopid = morder.shopid;
                mdt.wid = morder.wid;
                mdt.pay_time = DateTime.Now;
                int id = otTran.Add(mdt);
                if (id <= 0)
                {

                    //添加记录失败,记录日志
                    LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加转账记录失败,订单ID=", id));
                }
                LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加转账记录成功,订单ID=", id));
                // Transfer(mdt, morder);
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(typeof(ResultNotify), ex);
            }


        }

        private void SendMsg(MxWeiXinPF.Model.orders morder)
        {
            try
            {
                MxWeiXinPF.Model.users umodel = new MxWeiXinPF.BLL.wx_dt_user_BaseData().GetModelByOpenID(morder.openid);
                MxWeiXinPF.Model.manager mman = new MxWeiXinPF.BLL.manager().GetModel(morder.shopid);
                if (mman != null)
                {

                    if (!string.IsNullOrEmpty(mman.shopclerkid))
                    {
                        //如果指定了微信店长,则发送模板消息
                        if (!SendTemplateMsg("", morder, umodel, mman))
                        {//发送模版消息失败
                            SendSMMsg("", morder, umodel, mman);
                        }
                    }
                    else
                    {
                        if (!string.IsNullOrEmpty(mman.telephone))
                        {
                            SendSMMsg("", morder, umodel, mman);
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                LogHelper.WriteLog(typeof(ResultNotify), ex);
            }

        }


        private bool SendTemplateMsg(string content, MxWeiXinPF.Model.orders model, MxWeiXinPF.Model.users umodel, MxWeiXinPF.Model.manager mmodel)
        {
            if (mmodel == null)
            {
                return false;
            }

            content = string.Concat("你好,你的店铺:", mmodel.real_name, "的客户:", umodel.nick_name, "有一张订单付款成功了,请尽快安排发货");
            MxWeiXinPF.Model.wx_userweixin weixin = new MxWeiXinPF.BLL.wx_userweixin().GetModel(mmodel.agentId);
            if (weixin == null)
            {
                return false;
            }
            if (!AccessTokenContainer.CheckRegistered(weixin.AppId))
            {
                AccessTokenContainer.Register(weixin.AppId, weixin.AppSecret);
            }
            if (string.IsNullOrEmpty(mmodel.shopclerkid))
            {
                return false;
            }
            WxJsonResult ret = Senparc.Weixin.MP.AdvancedAPIs.CustomApi.SendText(weixin.AppId, mmodel.shopclerkid, content);
            if (ret.errcode == 0)
            {
                return true;
            }
            return false;
        }

        private bool SendSMMsg(string content, MxWeiXinPF.Model.orders model, MxWeiXinPF.Model.users umodel, MxWeiXinPF.Model.manager mmodel)
        {
            if (mmodel == null)
            {
                return false;
            }
            BlueSmsMgr sm = new BlueSmsMgr(39);
            content = string.Concat("你好,你的店铺:", mmodel.user_name, "的客户:", umodel.nick_name, "有一张订单付款成功了,请尽快安排发货");
            sm.SendSMS(mmodel.telephone, content);
            return false;
        }

        private bool Transfer(MxWeiXinPF.Model.dt_transfer mdt, MxWeiXinPF.Model.orders morder)
        {
            if (mdt == null)
            {
                return false;
            }
            MxWeiXinPF.BLL.manager bman = new MxWeiXinPF.BLL.manager();
            qypay pays = new qypay();
            MxWeiXinPF.BLL.dt_transfer btran = new MxWeiXinPF.BLL.dt_transfer();
            MxWeiXinPF.Model.manager mman = bman.GetModel(mdt.shopid);
            try
            {
                if (mman != null && !string.IsNullOrEmpty(mman.shopclerkid))
                {
                    string xml = pays.Transfer("1", morder.real_amount, mman.shopclerkid, mman.real_name);
                    SortedDictionary<string, object> mvals = FromXml(xml);
                    if (mvals == null)
                    {
                        //添加记录失败,记录日志
                        LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加企业向店铺转账记录失败，返回失败", mvals["return_msg"], mvals["result_code"], mvals["err_code"]));
                    }
                    if (mvals["return_code"].ToString().ToUpper() == "SUCCESS" && mvals["return_code"].ToString().ToUpper() == "SUCCESS" && mvals["return_msg"].ToString() == "") //返回失败
                    {
                        mdt.status = 1;
                        btran.Update(mdt);
                        LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加企业向店铺转账成功,订单号码为:", mdt.id.ToString()));
                    }
                    else
                    {
                        mdt.status = 0;
                        btran.Update(mdt);
                        //添加记录失败,记录日志
                        LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加企业向店铺转账记录失败，返回失败", mvals["return_msg"], mvals["result_code"], mvals["err_code"]));
                    }
                }
            }
            catch (Exception ex)
            {
                mdt.status = 0;
                btran.Update(mdt);
                LogHelper.WriteLog(typeof(ResultNotify), string.Concat("添加企业向店铺转账失败,", ex.Message));
            }


            return true;
        }

        public SortedDictionary<string, object> FromXml(string xml)
        {
            SortedDictionary<string, object> m_values = new SortedDictionary<string, object>();
            if (string.IsNullOrEmpty(xml))
            {
                return null;
            }

            XmlDocument xmlDoc = new XmlDocument();
            xmlDoc.LoadXml(xml);
            XmlNode xmlNode = xmlDoc.FirstChild;//获取到根节点<xml>
            XmlNodeList nodes = xmlNode.ChildNodes;
            foreach (XmlNode xn in nodes)
            {
                XmlElement xe = (XmlElement)xn;
                m_values[xe.Name] = xe.InnerText;//获取xml的键值对到WxPayData内部的数据中
            }
            return m_values;
        }
        //查询订单
        private bool QueryOrder(string transaction_id)
        {
            WxPayData req = new WxPayData();
            req.SetValue("transaction_id", transaction_id);
            WxPayData res = WxPayApi.OrderQuery(req);
            if (res.GetValue("return_code").ToString() == "SUCCESS" &&
                res.GetValue("result_code").ToString() == "SUCCESS")
            {
                return true;
            }
            else
            {
                return false;
            }
        }
    }
}